#pragma once
#include "Common.h"
namespace Simulation {
	class TimeIntegration
	{
	public:
		/** Perform an integration step for a particle using the semi-implicit Euler
		 * (symplectic Euler) method:
		 * \f{align*}{
		 * \mathbf{v}(t+h) &= \mathbf{v}(t) + \mathbf{a}(t) h\\
		 * \mathbf{x}(t+h) &= \mathbf{x}(t) + \mathbf{v}(t+h) h
		 * \f}
		 *
		 * @param  h time step size
		 * @param  mass mass of the particle
		 * @param  position position of the particle
		 * @param  velocity velocity of the particle
		 * @param  acceleration acceleration of the particle
		 */
		static void semiImplicitEuler(
			const double h,
			const double mass,
			glm::dvec3& position,
			glm::dvec3& velocity,
			const glm::dvec3& acceleration);

		// -------------- velocity update (first order) -----------------------------------------------------
		/** Perform a velocity update (first order) for the linear velocity:
		 * \f{equation*}{
		 * \mathbf{v}(t+h) = \frac{1}{h} (\mathbf{p}(t+h) - \mathbf{p}(t)
		 * \f}
		 *
		 * @param  h time step size
		 * @param  mass mass of the particle
		 * @param  position new position \f$\mathbf{p}(t+h)\f$ of the particle
		 * @param  oldPosition position \f$\mathbf{p}(t)\f$ of the particle before the time step
		 * @param  velocity resulting velocity of the particle
		 */
		static void velocityUpdateFirstOrder(
			const double h,
			const double mass,
			const glm::dvec3& position,				// position after constraint projection	at time t+h
			const glm::dvec3& oldPosition,				// position before constraint projection at time t
			glm::dvec3& velocity);



		// -------------- velocity update (second order) -----------------------------------------------------
		static void velocityUpdateSecondOrder(
			const double h,
			const double mass,
			const glm::dvec3& position,				// position after constraint projection	at time t+h
			const glm::dvec3& oldPosition,				// position before constraint projection at time t
			const glm::dvec3& positionOfLastStep,		// position of last simulation step at time t-h
			glm::dvec3& velocity);

	};

}

